package com.ruoyi.stuclient.api;

import cn.hutool.core.util.CharsetUtil;
import cn.hutool.crypto.digest.DigestUtil;
import cn.hutool.crypto.symmetric.AES;
import cn.hutool.jwt.JWT;
import com.alibaba.fastjson2.JSONObject;
import com.aliyun.dysmsapi20170525.models.SendSmsResponse;
import com.ruoyi.common.core.constant.CacheConstants;
import com.ruoyi.common.core.constant.Constants;
import com.ruoyi.common.core.context.ThirdSessionHolder;
import com.ruoyi.common.core.domain.ThirdSession;
import com.ruoyi.common.core.web.domain.AjaxResult;
import com.ruoyi.common.redis.service.RedisService;
import com.ruoyi.stuclient.domain.EwcCourseGrouping;
import com.ruoyi.stuclient.domain.EwcStudent;
import com.ruoyi.stuclient.domain.dto.SMSGetDto;
import com.ruoyi.stuclient.domain.dto.StudentLoginDto;
import com.ruoyi.stuclient.domain.dto.StudentLoginResetPwdDto;
import com.ruoyi.stuclient.domain.dto.StudentResetPwdDto;
import com.ruoyi.stuclient.domain.vo.StudentGroupVo;
import com.ruoyi.stuclient.domain.vo.StudentLoginVo;
import com.ruoyi.stuclient.service.*;
import com.ruoyi.stuclient.utils.aliyunUtil.SMSUtil;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import lombok.extern.slf4j.Slf4j;
import org.jetbrains.annotations.NotNull;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;


import javax.validation.Valid;
import javax.validation.constraints.NotBlank;
import java.util.Objects;
import java.util.concurrent.TimeUnit;

import static com.ruoyi.stuclient.utils.aliyunUtil.SMSUtil.secureRandom6;

/**
 * 学生端小组联系和课后作业接口
 * @author zsp
 * @date 2025年03月18日 06：34
 */
@Slf4j
@Validated
@RestController
@Tag(name = "学生端接口")
@RequestMapping("/api/studentClient")
public class StudentClientApi {

    @Value("${sms.SMSCodeVerification}")
    private String SMSCodeVerification;

    //短信间隔时间阈值 毫秒
    @Value("${sms.SMSCodeTimeGapLimit}")
    private String SMSCodeTimeGapLimit;

    //短信间隔时间阈值内可获取最大次数
    @Value("${sms.SMSCodeCountGapLimit}")
    private String SMSCodeCountGapLimit;

    //单次获取短信允许验证错误失败次数
    @Value("${sms.SMSCodeErrorCountLimit}")
    private String SMSCodeErrorCountLimit;

    @Autowired
    private IEwcStudentGroupService iEwcStudentGroupService;

    @Autowired
    private IEwcStudentService iEwcStudentService;

    @Autowired
    private IEwcSmsTemplateService iEwcSmsTemplateService;

    @Autowired
    private IEwcSmsFlowService iEwcSmsFlowService;

    @Autowired
    private IEwcClientControlService iEwcClientControlService;

    @Autowired
    private RedisService redisService;

    @Autowired
    private SMSUtil smsUtil;

    /**
     * 获取学生信息
     * @param studentNo
     * @return AjaxResult
     */
    @Operation(summary = "获取学生信息")
    @GetMapping("/getStudentInfo")
    public AjaxResult getStudentInfo(@NotBlank(message = "学号不能为空") String studentNo) {
        EwcStudent studentInfo = iEwcStudentService.getStudentInfoByStudentNo(studentNo);
        if(Objects.nonNull(studentInfo)){
            return AjaxResult.success("查询成功", studentInfo);
        }else{
            return AjaxResult.error("学号有误");
        }
    }
    /**
     * 获取验证码
     * @param smsGetDto
     * @return AjaxResult
     */
    @Operation(summary = "获取验证码")
    @PostMapping("/getSMSCode")
    public AjaxResult getStudentInfo(@Valid @RequestBody SMSGetDto smsGetDto) throws Exception {
        JSONObject resultJson = new JSONObject();
        String flowId = "";
        if(Objects.equals("true",SMSCodeVerification)){
            //1.用户控制表验证
//            iEwcClientControlService.controlValid(smsGetDto);
            //1.生成6位验证码
            String smsCode = secureRandom6();
            //2.获取手机号
            String mobileNo = iEwcStudentService.getClientMobileNo(smsGetDto);
            //3.获取模板内容
            String templateContent = iEwcSmsTemplateService.getTemplateContent(smsGetDto);
            if(templateContent == null){
                return AjaxResult.error("消息模板不存在");
            }
            //4.发送短信
            SendSmsResponse sendSmsResponse = smsUtil.sendSMSCode(mobileNo,smsCode);
            if(sendSmsResponse != null && sendSmsResponse.getBody() != null
                    && Objects.equals("OK",sendSmsResponse.getBody().getCode())){//成功
                //5.验证码信息入库
                flowId = iEwcSmsFlowService.saveSMSCode(smsGetDto,mobileNo,smsCode,templateContent,sendSmsResponse.getBody().getRequestId());
            }
            if(Objects.equals("",flowId)){
                return AjaxResult.error("验证码获取失败");
            }
        }
        resultJson.put("flowId", flowId);
        return AjaxResult.success("获取成功", resultJson);
    }

    /**
     * 学生密码重置
     * @param studentResetPwdDto
     * @return AjaxResult
     */
    @Operation(summary = "学生密码重置")
    @PostMapping("/studentResetPwd")
    public AjaxResult studentResetPwd(@NotNull @Valid @RequestBody StudentResetPwdDto studentResetPwdDto) {
        //1.校验密码与确认密码是否一致
        if(!Objects.equals(studentResetPwdDto.getNewPassword(),studentResetPwdDto.getConfirmPassword())){
            return AjaxResult.error("新密码与确认密码不一致");
        }
        //2.校验手机验证码
        if(Objects.equals("true",SMSCodeVerification)){
            AjaxResult result = iEwcSmsFlowService.validateSMSCode(studentResetPwdDto);
            if(result.isError()){
                return result;
            }
        }
        //3.重置登录密码
        //解密密码
        AES aes = new AES("CBC", "PKCS7Padding", Constants.AES_KEY.getBytes(), Constants.AES_IV.getBytes());
        String password=aes.decryptStr(studentResetPwdDto.getNewPassword(), CharsetUtil.CHARSET_UTF_8);
        boolean result = iEwcStudentService.resetLoginPassword(studentResetPwdDto,DigestUtil.md5Hex(password));
        if(result){
            return AjaxResult.success("密码已重置");
        }else {
            return AjaxResult.error("提交失败");
        }
    }

    /**
     * 获取学生设置页面信息
     * @return AjaxResult
     */
    @Operation(summary = "获取学生设置页面信息")
    @GetMapping("/getStudentSettingInfo")
    public AjaxResult getStudentSettingInfo(){
        EwcStudent studentInfo = iEwcStudentService.getStudentSettingInfo();
        if(Objects.nonNull(studentInfo)){
            return AjaxResult.success("查询成功", studentInfo);
        }else{
            return AjaxResult.error("提交数据有误");
        }
    }
    /**
     * 重置学生基本信息
     * @return AjaxResult
     */
    @Operation(summary = "重置学生基本信息")
    @PostMapping("/resetStudentSettingInfo")
    public AjaxResult resetStudentSettingInfo(@RequestBody EwcStudent studentInfo){
        if(Objects.nonNull(studentInfo)){
            System.out.println(studentInfo.toString());
            boolean result = iEwcStudentService.resetStudentSettingInfo(studentInfo);
            if(result){
                return AjaxResult.success("信息已重置");
            }
        }
        return AjaxResult.error("提交数据有误");
    }

    /**
     * 登录状态重置学生密码
     * @return AjaxResult
     */
    @Operation(summary = "登录状态重置学生密码")
    @PostMapping("/studentLoginResetPwd")
    public AjaxResult studentLoginResetPwd(@NotNull @Valid @RequestBody StudentLoginResetPwdDto studentLoginResetPwdDto){
        //1.校验密码与确认密码是否一致
        if(!Objects.equals(studentLoginResetPwdDto.getNewPassword(),studentLoginResetPwdDto.getConfirmPassword())){
            return AjaxResult.error("新密码与确认密码不一致");
        }
        //2.校验密码是否正确
        AES aes = new AES("CBC", "PKCS7Padding", Constants.AES_KEY.getBytes(), Constants.AES_IV.getBytes());
        String password=aes.decryptStr(studentLoginResetPwdDto.getOldPassword(), CharsetUtil.CHARSET_UTF_8);
        StudentLoginVo studentLoginVo = iEwcStudentService.getLoginInfoByStudentNo(ThirdSessionHolder.getThirdSession().getStudentNo());
        if (Objects.isNull(studentLoginVo) || !Objects.equals(studentLoginVo.getPassword(), DigestUtil.md5Hex(password))){
            return AjaxResult.error("账户或密码错误");
        }
        //3.重置登录密码
        //解密密码
        AES aes2 = new AES("CBC", "PKCS7Padding", Constants.AES_KEY.getBytes(), Constants.AES_IV.getBytes());
        String passwordNew=aes.decryptStr(studentLoginResetPwdDto.getNewPassword(), CharsetUtil.CHARSET_UTF_8);
        StudentResetPwdDto studentResetPwdDto = new StudentResetPwdDto();
        studentResetPwdDto.setStudentNo(ThirdSessionHolder.getThirdSession().getStudentNo());
        boolean result = iEwcStudentService.resetLoginPassword(studentResetPwdDto,DigestUtil.md5Hex(passwordNew));
        if(result){
            return AjaxResult.success("密码已重置");
        }else {
            return AjaxResult.error("提交失败");
        }
    }
}
